package com.micro.ai.gateway.controller;

import com.micro.ai.commons.domain.ApiResponse;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.refresh.ContextRefresher;
import org.springframework.web.bind.annotation.*;
import reactor.core.publisher.Mono;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;

/**
 * 配置管理控制器
 * 提供配置查询和手动刷新功能
 * 
 * @author micro-ai
 * @since 0.0.1
 */
@Slf4j
@RestController
@RequestMapping("/config-management")
public class ConfigManagementController {

    @Autowired
    private ContextRefresher contextRefresher;

    // 限流配置
    @Value("${rate-limit.default-limit:100}")
    private Integer rateLimitDefaultLimit;

    @Value("${rate-limit.default-window:60}")
    private Integer rateLimitDefaultWindow;

    // JWT配置
    @Value("${jwt.secret:default-secret}")
    private String jwtSecret;

    @Value("${jwt.expiration:86400}")
    private Long jwtExpiration;

    // 签名验证配置
    @Value("${signature.enabled:false}")
    private Boolean signatureEnabled;

    @Value("${signature.timeout:300}")
    private Long signatureTimeout;

    // IP过滤配置
    @Value("${ip-filter.enabled:false}")
    private Boolean ipFilterEnabled;

    @Value("${ip-filter.whitelist-enabled:false}")
    private Boolean ipFilterWhitelistEnabled;

    @Value("${ip-filter.blacklist-enabled:true}")
    private Boolean ipFilterBlacklistEnabled;

    /**
     * 获取当前配置信息
     */
    @GetMapping("/current")
    public Mono<ApiResponse<Map<String, Object>>> getCurrentConfig() {
        log.info("查询当前网关配置");
        
        Map<String, Object> config = new LinkedHashMap<>();
        
        // 限流配置
        Map<String, Object> rateLimit = new LinkedHashMap<>();
        rateLimit.put("defaultLimit", rateLimitDefaultLimit);
        rateLimit.put("defaultWindow", rateLimitDefaultWindow);
        config.put("rateLimit", rateLimit);
        
        // JWT配置
        Map<String, Object> jwt = new LinkedHashMap<>();
        jwt.put("secret", maskSensitive(jwtSecret));
        jwt.put("expiration", jwtExpiration);
        config.put("jwt", jwt);
        
        // 签名验证配置
        Map<String, Object> signature = new LinkedHashMap<>();
        signature.put("enabled", signatureEnabled);
        signature.put("timeout", signatureTimeout);
        config.put("signature", signature);
        
        // IP过滤配置
        Map<String, Object> ipFilter = new LinkedHashMap<>();
        ipFilter.put("enabled", ipFilterEnabled);
        ipFilter.put("whitelistEnabled", ipFilterWhitelistEnabled);
        ipFilter.put("blacklistEnabled", ipFilterBlacklistEnabled);
        config.put("ipFilter", ipFilter);
        
        config.put("updateTime", LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
        
        return Mono.just(ApiResponse.success(config));
    }

    /**
     * 手动刷新配置
     */
    @PostMapping("/refresh")
    public Mono<ApiResponse<RefreshResult>> refreshConfig() {
        log.info("手动触发配置刷新");
        
        try {
            Set<String> refreshedKeys = contextRefresher.refresh();
            
            RefreshResult result = new RefreshResult();
            result.setSuccess(true);
            result.setRefreshedKeys(new ArrayList<>(refreshedKeys));
            result.setRefreshTime(LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
            result.setMessage(String.format("成功刷新 %d 个配置项", refreshedKeys.size()));
            
            log.info("配置刷新完成: {}", result.getMessage());
            
            return Mono.just(ApiResponse.success(result));
        } catch (Exception e) {
            log.error("配置刷新失败", e);
            
            RefreshResult result = new RefreshResult();
            result.setSuccess(false);
            result.setMessage("配置刷新失败: " + e.getMessage());
            result.setRefreshTime(LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
            
            return Mono.just(ApiResponse.error("C0001", "配置刷新失败"));
        }
    }

    /**
     * 获取配置刷新历史（简化版）
     */
    @GetMapping("/refresh-history")
    public Mono<ApiResponse<List<String>>> getRefreshHistory() {
        log.info("查询配置刷新历史");
        
        // 这里简化处理，实际应该从数据库或缓存中获取历史记录
        List<String> history = Arrays.asList(
                "配置刷新历史记录需要额外的存储实现",
                "建议使用数据库或Redis存储刷新记录",
                "当前时间: " + LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"))
        );
        
        return Mono.just(ApiResponse.success(history));
    }

    /**
     * 验证配置合法性
     */
    @PostMapping("/validate")
    public Mono<ApiResponse<ValidationResult>> validateConfig(@RequestBody Map<String, Object> config) {
        log.info("验证配置: {}", config);
        
        ValidationResult result = new ValidationResult();
        result.setValid(true);
        result.setErrors(new ArrayList<>());
        
        // 验证限流配置
        if (config.containsKey("rate-limit.default-limit")) {
            Object limit = config.get("rate-limit.default-limit");
            if (!(limit instanceof Integer) || (Integer) limit <= 0) {
                result.setValid(false);
                result.getErrors().add("rate-limit.default-limit 必须是大于0的整数");
            }
        }
        
        // 验证JWT过期时间
        if (config.containsKey("jwt.expiration")) {
            Object expiration = config.get("jwt.expiration");
            if (!(expiration instanceof Integer) || (Integer) expiration <= 0) {
                result.setValid(false);
                result.getErrors().add("jwt.expiration 必须是大于0的整数");
            }
        }
        
        // 验证签名超时时间
        if (config.containsKey("signature.timeout")) {
            Object timeout = config.get("signature.timeout");
            if (!(timeout instanceof Integer) || (Integer) timeout <= 0) {
                result.setValid(false);
                result.getErrors().add("signature.timeout 必须是大于0的整数");
            }
        }
        
        result.setMessage(result.isValid() ? "配置验证通过" : "配置验证失败");
        
        return Mono.just(ApiResponse.success(result));
    }

    /**
     * 获取配置模板
     */
    @GetMapping("/template")
    public Mono<ApiResponse<Map<String, Object>>> getConfigTemplate() {
        log.info("获取配置模板");
        
        Map<String, Object> template = new LinkedHashMap<>();
        
        // 限流配置模板
        Map<String, Object> rateLimit = new LinkedHashMap<>();
        rateLimit.put("default-limit", 100);
        rateLimit.put("default-window", 60);
        rateLimit.put("description", "限流配置：default-limit为每个窗口期的最大请求数，default-window为窗口期时长（秒）");
        template.put("rate-limit", rateLimit);
        
        // JWT配置模板
        Map<String, Object> jwt = new LinkedHashMap<>();
        jwt.put("secret", "your-secret-key-here");
        jwt.put("expiration", 86400);
        jwt.put("description", "JWT配置：secret为签名密钥，expiration为令牌有效期（秒）");
        template.put("jwt", jwt);
        
        // 签名验证配置模板
        Map<String, Object> signature = new LinkedHashMap<>();
        signature.put("enabled", false);
        signature.put("timeout", 300);
        signature.put("description", "签名验证配置：enabled为是否启用，timeout为签名有效期（秒）");
        template.put("signature", signature);
        
        // IP过滤配置模板
        Map<String, Object> ipFilter = new LinkedHashMap<>();
        ipFilter.put("enabled", false);
        ipFilter.put("whitelist-enabled", false);
        ipFilter.put("blacklist-enabled", true);
        ipFilter.put("description", "IP过滤配置：enabled为总开关，whitelist-enabled为白名单模式，blacklist-enabled为黑名单模式");
        template.put("ip-filter", ipFilter);
        
        return Mono.just(ApiResponse.success(template));
    }

    /**
     * 脱敏处理敏感信息
     */
    private String maskSensitive(String value) {
        if (value == null || value.length() <= 8) {
            return "******";
        }
        return value.substring(0, 4) + "****" + value.substring(value.length() - 4);
    }

    @Data
    public static class RefreshResult {
        private boolean success;
        private String message;
        private List<String> refreshedKeys;
        private String refreshTime;
    }

    @Data
    public static class ValidationResult {
        private boolean valid;
        private String message;
        private List<String> errors;
    }
}

